package com.alinesno.cloud.operation.cmdb.third.wechat.controller;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.codec.digest.DigestUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import com.alinesno.cloud.operation.cmdb.common.util.SpringContext;
import com.alinesno.cloud.operation.cmdb.controller.BaseController;
import com.alinesno.cloud.operation.cmdb.entity.WechatMessageEntity;
import com.alinesno.cloud.operation.cmdb.service.WechatMessageService;

import me.chanjar.weixin.mp.bean.message.WxMpXmlMessage;

/**
 * 微信api
 * @author WeiXiaoJin
 * @since 2018年8月10日 上午12:14:55
 */
@Controller    
public class WechatApiController extends BaseController {

	private static final Logger logger = LoggerFactory.getLogger(WechatApiController.class) ; 
	
	@Value("${wechat.token}")  
	private String wechatToken; 
	
	@Autowired
	private WechatMessageService wechatMessageService ; 
	
	/**
	 * 构造微信重定向路径
	 */
	@ResponseBody
	@RequestMapping(name="/wechat_token" , produces = "text/json;charset=UTF-8")
    public Object tokenCheck(HttpServletRequest request,HttpServletResponse response) throws IOException{
	
		logger.debug("微信推送接口:{}" , request.getMethod());
		
		if("GET".equals(request.getMethod())) {
			
			String signature = request.getParameter("signature");
			String timestamp = request.getParameter("timestamp");
			String nonce = request.getParameter("nonce");
			String echostr = request.getParameter("echostr");
			
			echostr = tokenCheck(signature, timestamp, nonce, echostr);
			return echostr ; 
			
		}else if("POST".equals(request.getMethod())) {
			logger.debug("消息推送.");
			//获取消息流
			WxMpXmlMessage message = WxMpXmlMessage.fromXml(request.getInputStream());
			String messageType=message.getMsgType();   //消息类型
			String fromUser=message.getFromUser() ; //发送者帐号
			String toUser=message.getToUser() ; //开发者微信号
			String content=message.getContent();//文本消息  文本内容
			String event = message.getEvent() ; 
		
			try {
				WechatMessageEntity wechatMessageEntity = new WechatMessageEntity() ; 
				BeanUtils.copyProperties(message, wechatMessageEntity); 
				wechatMessageService.save(wechatMessageEntity) ; 
				
				WechatMessageBase messageService = (WechatMessageBase) SpringContext.getBean("wechat_message_"+messageType) ; 
				return messageService.handlerMessage(message , fromUser , toUser , event , content) ; 
			}catch(Exception e) {
				logger.error("没有微信服务:{}" , e.getMessage());
			}
			
		}
		return "SUCCESS" ;
		
    }
	
	 /**
     * 验证接口配置信息
     * 加密/校验流程如下：
    1. 将token、timestamp、nonce三个参数进行字典序排序
    2. 将三个参数字符串拼接成一个字符串进行sha1加密
    3. 开发者获得加密后的字符串可与signature对比，标识该请求来源于微信
     */
    public String tokenCheck(String signature,String timestamp,String nonce,String echostr){
        List<String> list = new ArrayList<>();
        list.add(timestamp);
        list.add(wechatToken);
        list.add(nonce);
        
        Collections.sort(list);//1.字典排序
        
        String str = DigestUtils.sha1Hex(list.get(0)+list.get(1)+list.get(2));//2.sha1加密
        if(signature.equals(str)){//3.判断是否微信信息  此处判断echostr!=null是为了进行下面的操作不影响此处原本的效果
            return echostr;
            //    也就是说 如果echostr!=null，那么此次的请求是在验证是否成为开发者的；否则就是其他的微信请求，不用跳出程序
        }
        return null;
    }
}
